/********************************************************************************************************
 * @file AdvertisingDeviceListFragment.java
 *
 * @brief for TLSR chips
 *
 * @author telink
 * @date Sep. 30, 2019
 *
 * @par Copyright (c) 2019, Telink Semiconductor (Shanghai) Co., Ltd. ("TELINK")
 *
 *          Licensed under the Apache License, Version 2.0 (the "License");
 *          you may not use this file except in compliance with the License.
 *          You may obtain a copy of the License at
 *
 *              http://www.apache.org/licenses/LICENSE-2.0
 *
 *          Unless required by applicable law or agreed to in writing, software
 *          distributed under the License is distributed on an "AS IS" BASIS,
 *          WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 *          See the License for the specific language governing permissions and
 *          limitations under the License.
 *******************************************************************************************************/
package com.telink.lt.ui;

import android.bluetooth.BluetoothAdapter;
import android.bluetooth.BluetoothDevice;
import android.content.Intent;
import android.content.pm.PackageInfo;
import android.content.pm.PackageManager;
import android.os.Bundle;
import android.os.Handler;
import android.os.Message;
import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;
import android.widget.ProgressBar;
import android.widget.TextView;

import com.telink.lt.AdvertisingDevice;
import com.telink.lt.R;
import com.telink.lt.TelinkLog;
import com.telink.lt.adapter.AdvertisingDeviceListAdapter;
import com.telink.lt.adapter.BaseRecyclerViewAdapter;
import com.telink.ota.util.Arrays;

import java.util.ArrayList;
import java.util.List;

import androidx.annotation.NonNull;
import androidx.annotation.Nullable;
import androidx.appcompat.widget.Toolbar;
import androidx.recyclerview.widget.LinearLayoutManager;
import androidx.recyclerview.widget.RecyclerView;

public class AdvertisingDeviceListFragment extends BaseFragment {

    private AdvertisingDeviceListAdapter listAdapter;
    private List<AdvertisingDevice> deviceList = new ArrayList<>();

    private final Handler mScanHandler = new Handler();
    private BluetoothAdapter mBluetoothAdapter;
    private final static long SCAN_PERIOD = 10 * 1000;
    private boolean mScanning = false;
    RecyclerView recyclerView;
    private ProgressBar pb_refreshing;
    private Toolbar toolbar;

    @Nullable
    @Override
    public View onCreateView(@NonNull LayoutInflater inflater, @Nullable ViewGroup container, @Nullable Bundle savedInstanceState) {
        return inflater.inflate(R.layout.fragment_device_list, null);
    }

    @Override
    public void onViewCreated(@NonNull View view, @Nullable Bundle savedInstanceState) {
        super.onViewCreated(view, savedInstanceState);
        recyclerView = view.findViewById(R.id.rv_list);
        pb_refreshing = view.findViewById(R.id.pb_refreshing);
        TextView tv_title = view.findViewById(R.id.tv_title);
        tv_title.setText(R.string.advertising_title);
        toolbar = view.findViewById(R.id.title_bar);
        toolbar.inflateMenu(R.menu.menu_main_title);
        toolbar.getMenu().findItem(R.id.item_version).setTitle(getVersion());
        toolbar.setNavigationIcon(R.drawable.ic_refresh);
        toolbar.setNavigationOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View view) {
                scanToggle(!mScanning);
//                refresh();
            }
        });
        deviceList = new ArrayList<>();
        listAdapter = new AdvertisingDeviceListAdapter(getActivity(), deviceList);
        recyclerView.setLayoutManager(new LinearLayoutManager(getActivity()));
        recyclerView.setAdapter(listAdapter);

        listAdapter.setOnItemClickListener(new BaseRecyclerViewAdapter.OnItemClickListener() {
            @Override
            public void onItemClick(int position) {

                if (mScanning) {
                    scanToggle(false);
                }

                startActivity(new Intent(getActivity(), OtaActivity.class)
                        .putExtra("device", deviceList.get(position).device));
            }
        });
    }

    public void setBluetoothAdapter(BluetoothAdapter bluetoothAdapter) {
        this.mBluetoothAdapter = bluetoothAdapter;
    }

    private void scanToggle(final boolean enable) {
        mScanHandler.removeCallbacks(scanTask);
        if (enable) {
            TelinkLog.i("ADV#startScan");
            mScanning = true;
            deviceList.clear();
            listAdapter.notifyDataSetChanged();

            mBluetoothAdapter.startLeScan(scanCallback);
            mScanHandler.postDelayed(scanTask, SCAN_PERIOD);
        } else {
            TelinkLog.i("ADV#stopScan");
            mScanning = false;
            mBluetoothAdapter.stopLeScan(scanCallback);
        }
        toolbar.setNavigationIcon(mScanning ? R.drawable.ic_stop : R.drawable.ic_refresh);
        pb_refreshing.setVisibility(mScanning ? View.VISIBLE : View.INVISIBLE);

    }


    @Override
    public void onDestroy() {
        super.onDestroy();
        if (mScanning && mBluetoothAdapter != null && mBluetoothAdapter.isEnabled()) {
            mBluetoothAdapter.stopLeScan(scanCallback);
        }
    }

    @Override
    public void onHiddenChanged(boolean hidden) {
        super.onHiddenChanged(hidden);
        if (hidden && mScanning){
            scanToggle(false);
        }
    }

    private BluetoothAdapter.LeScanCallback scanCallback = new BluetoothAdapter.LeScanCallback() {
        @Override
        public void onLeScan(final BluetoothDevice device, final int rssi, final byte[] scanRecord) {
            TelinkLog.w("scan:" + device.getName() + " mac:" + device.getAddress() + " rssi:" + rssi + " record:  " + Arrays.bytesToHexString(scanRecord, ":"));
//            if (!device.getAddress().toUpperCase().contains("FF:FF:BB:CC:DD")) return; // for dev
            for (AdvertisingDevice advDevice: deviceList) {
                if (device.getAddress().equals(advDevice.device.getAddress())) {
                    /*if (advDevice.rssi != rssi) {
                        advDevice.rssi = rssi;
                    }*/
                    return;
                }
            }

            deviceList.add(new AdvertisingDevice(device, rssi, scanRecord));
            listAdapter.notifyItemInserted(deviceList.size() - 1);
//            refreshHandler.obtainMessage(-1).sendToTarget();

        }
    };

    private Runnable scanTask = new Runnable() {
        @Override
        public void run() {
            if (mBluetoothAdapter != null && mBluetoothAdapter.isEnabled()) {
                scanToggle(false);
            }
        }
    };

    private String getVersion() {
        try {
            PackageManager manager = this.getActivity().getPackageManager();
            PackageInfo info = manager.getPackageInfo(this.getActivity().getPackageName(), 0);
            String version = info.versionName;
            return "V" + version;
        } catch (Exception e) {
            e.printStackTrace();
            return "";
        }
    }
}
